package com.recharge.filters;

import com.alibaba.fastjson.JSONObject;
import com.recharge.common.enums.ErrorCode;
import com.recharge.common.result.web.ObjectResponse;
import com.recharge.common.util.*;
import com.recharge.domain.vo.UserLoginDO;
import org.apache.commons.lang3.StringUtils;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.web.filter.authc.UserFilter;
import org.apache.shiro.web.util.WebUtils;

import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 * 自定义token过滤器
 */
public class TokenCheckFilter extends UserFilter {

    private Logger logger = LoggerFactory.getLogger(this.getClass().getName());

    RedisUtil redisUtil;

    public TokenCheckFilter(RedisUtil redisUtil){
        this.redisUtil = redisUtil;
    }
    /**
     * 判断是否拥有权限 true:认证成功  false:认证失败
     * mappedValue 访问该url时需要的权限
     * subject.isPermitted 判断访问的用户是否拥有mappedValue权限
     */
    @Override
    public boolean isAccessAllowed(ServletRequest request, ServletResponse response, Object mappedValue) {
        // 根据请求头拿到token
        String token = WebUtils.toHttp(request).getHeader(Constant.AUTH_TOKEN);
        if(StringUtils.isEmpty(token)){
            return false;
        }
        UserLoginDO user = (UserLoginDO) SecurityUtils.getSubject().getPrincipal();
        if(user == null){
            return false;
        }
        if(!token.equals(user.getToken())){
            return false;
        }
        return true;
    }

    /**
     * 401非法请求
     *
     * @param request
     * @param msg
     *
     */
    private void responseCode(ServletRequest request, ServletResponse response, int code,String msg) {
        try {
            HttpServletResponse httpServletResponse = (HttpServletResponse) response;
            httpServletResponse.setCharacterEncoding("UTF-8");
            httpServletResponse.setContentType("application/json; charset=utf-8");
            PrintWriter writer = httpServletResponse.getWriter();
            ObjectResponse<?> responseData = new ObjectResponse<>();
            responseData.setStatus(code);
            responseData.setMsg(msg);
            writer.write(JSONObject.toJSONString(responseData));
            writer.flush();
            writer.close();
        } catch (IOException e) {
            logger.debug(e.getMessage());
        }
    }

    /**
     * 认证失败回调的方法: 如果登录实体为null就保存请求和跳转登录页面,否则就跳转无权限配置页面
     */
    @Override
    protected boolean onAccessDenied(ServletRequest request, ServletResponse response) throws IOException {
        this.responseCode(request, response, ErrorCode.NOT_LOGIN.getCode(), ErrorCode.NOT_LOGIN.getMsg());
        return false;
    }

}
